/**
 * Copyright (c) 2011-2019, James Zhan 詹波 (jfinal@126.com).
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 * http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */
package com.jfinal.ext.kit

import com.jfinal.kit.StrKit
import com.jfinal.ext.kit.DateKit
import freemarker.template.utility.DateUtil
import java.lang.IllegalArgumentException
import java.text.ParseException
import java.text.SimpleDateFormat
import java.util.*
import kotlin.jvm.JvmOverloads

/**
 * DateKit.
 */
object DateKit {
    var datePattern = "yyyy-MM-dd"
    var timeStampPattern = "yyyy-MM-dd HH:mm:ss"

    @JvmName("setDatePattern1")
    fun setDatePattern(datePattern: String) {
        require(!StrKit.isBlank(datePattern)) { "datePattern can not be blank" }
        DateKit.datePattern = datePattern
    }

    @JvmName("setTimeStampPattern1")
    fun setTimeStampPattern(timeStampPattern: String) {
        require(!StrKit.isBlank(timeStampPattern)) { "timeStampPattern can not be blank" }
        DateKit.timeStampPattern = timeStampPattern
    }

    fun toDate(dateStr: String): Date? {
        var dateStr = dateStr
        if (StrKit.isBlank(dateStr)) {
            return null
        }
        dateStr = dateStr.trim { it <= ' ' }
        val length = dateStr.length
        return try {
            if (length == timeStampPattern.length) {
                val sdf = SimpleDateFormat(timeStampPattern)
                try {
                    sdf.parse(dateStr)
                } catch (e: ParseException) {
                    dateStr = dateStr.replace(".", "-")
                    dateStr = dateStr.replace("/", "-")
                    sdf.parse(dateStr)
                }
            } else if (length == datePattern.length) {
                val sdfDate = SimpleDateFormat(datePattern)
                try {
                    sdfDate.parse(dateStr)
                } catch (e: ParseException) {
                    dateStr = dateStr.replace(".", "-")
                    dateStr = dateStr.replace("/", "-")
                    sdfDate.parse(dateStr)
                }
            } else {
                throw IllegalArgumentException("The date format is not supported for the time being")
            }
        } catch (e: ParseException) {
            throw IllegalArgumentException("The date format is not supported for the time being")
        }
    }

    @kotlin.jvm.JvmOverloads
    public final fun getLastDay(
        d: java.util.Date?,
        n: kotlin.Int = 1
    ): java.util.Date {
        val cal = Calendar.getInstance()
        cal.time = d ?: Date()
        cal.add(Calendar.DAY_OF_MONTH, n * -1)
        return cal.time
    }

    @kotlin.jvm.JvmOverloads
    public final fun getLastDayStr(
        ds: kotlin.String,
        n: kotlin.Int = 1
    ): kotlin.String {
        return toStr(getLastDay(toDate(ds), n))
    }

    @kotlin.jvm.JvmOverloads
    public final fun getNextDay(
        d: java.util.Date,
        n: kotlin.Int=-1
    ): java.util.Date {
        return getLastDay(d,n)
    }

    @kotlin.jvm.JvmOverloads
    public final fun getNextDayStr(
        ds: kotlin.String,
        n: kotlin.Int =-1
    ): kotlin.String {
        return toStr(getLastDay(toDate(ds), n))
    }

    @JvmOverloads
    fun toStr(date: Date?, pattern: String? = datePattern): String {
        val sdf = SimpleDateFormat(pattern)
        return sdf.format(date)
    }
}